{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h1> Structured data prediction using Cloud ML Engine </h1>\n",
    "\n",
    "This notebook illustrates:\n",
    "<ol>\n",
    "<li> Exploring a BigQuery dataset using Datalab\n",
    "<li> Creating datasets for Machine Learning using Dataflow\n",
    "<li> Creating a model using the high-level Estimator API \n",
    "<li> Training on Cloud ML Engine\n",
    "<li> Deploying model\n",
    "<li> Predicting with model\n",
    "</ol>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Before starting the lab, upgrade packages that are required for this notebook."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "%%bash\n",
    "pip install --upgrade tensorflow==1.4\n",
    "pip install --ignore-installed --upgrade pytz==2018.4\n",
    "pip uninstall -y google-cloud-dataflow\n",
    "pip install --upgrade apache-beam[gcp]==2.6"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "**Now you have to restart the kernel by clicking the \"Reset Session\" in the menu bar** to reflect the newly installed modules.\n",
    "\n",
    "After restarting the kernel, you can resume the code execution from the next cell."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [],
   "source": [
    "# change these to try this notebook out\n",
    "BUCKET = 'cloud-training-demos-ml'\n",
    "PROJECT = 'cloud-training-demos'\n",
    "REGION = 'us-central1'"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [],
   "source": [
    "import os\n",
    "os.environ['BUCKET'] = BUCKET\n",
    "os.environ['PROJECT'] = PROJECT\n",
    "os.environ['REGION'] = REGION"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "%bash\n",
    "gcloud config set project $PROJECT\n",
    "gcloud config set compute/region $REGION"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "%%bash\n",
    "if ! gcloud storage ls | grep -q gs://${BUCKET}/; then\n",    "  gcloud storage buckets create --location=${REGION} gs://${BUCKET}\n",    "fi"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h1>Part 1: Data Analysis and Preparation</h1>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h2> Exploring data </h2>\n",
    "\n",
    "The data is natality data (record of births in the US). My goal is to predict the baby's weight given a number of factors about the pregnancy and the baby's mother.  Later, we will want to split the data into training and eval datasets. The hash of the year-month will be used for that."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [],
   "source": [
    "query=\"\"\"\n",
    "SELECT\n",
    "  weight_pounds,\n",
    "  is_male,\n",
    "  mother_age,\n",
    "  plurality,\n",
    "  gestation_weeks,\n",
    "  FARM_FINGERPRINT(CONCAT(CAST(YEAR AS STRING), CAST(month AS STRING))) AS hashmonth\n",
    "FROM\n",
    "  publicdata.samples.natality\n",
    "WHERE year > 2000\n",
    "\"\"\""
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/html": [
       "<div>\n",
       "<style scoped>\n",
       "    .dataframe tbody tr th:only-of-type {\n",
       "        vertical-align: middle;\n",
       "    }\n",
       "\n",
       "    .dataframe tbody tr th {\n",
       "        vertical-align: top;\n",
       "    }\n",
       "\n",
       "    .dataframe thead th {\n",
       "        text-align: right;\n",
       "    }\n",
       "</style>\n",
       "<table border=\"1\" class=\"dataframe\">\n",
       "  <thead>\n",
       "    <tr style=\"text-align: right;\">\n",
       "      <th></th>\n",
       "      <th>weight_pounds</th>\n",
       "      <th>is_male</th>\n",
       "      <th>mother_age</th>\n",
       "      <th>plurality</th>\n",
       "      <th>gestation_weeks</th>\n",
       "      <th>hashmonth</th>\n",
       "    </tr>\n",
       "  </thead>\n",
       "  <tbody>\n",
       "    <tr>\n",
       "      <th>0</th>\n",
       "      <td>3.562670</td>\n",
       "      <td>True</td>\n",
       "      <td>25</td>\n",
       "      <td>1</td>\n",
       "      <td>30</td>\n",
       "      <td>-1403073183891835564</td>\n",
       "    </tr>\n",
       "    <tr>\n",
       "      <th>1</th>\n",
       "      <td>3.999185</td>\n",
       "      <td>False</td>\n",
       "      <td>30</td>\n",
       "      <td>1</td>\n",
       "      <td>32</td>\n",
       "      <td>-7146494315947640619</td>\n",
       "    </tr>\n",
       "    <tr>\n",
       "      <th>2</th>\n",
       "      <td>7.438397</td>\n",
       "      <td>True</td>\n",
       "      <td>13</td>\n",
       "      <td>1</td>\n",
       "      <td>34</td>\n",
       "      <td>-7146494315947640619</td>\n",
       "    </tr>\n",
       "    <tr>\n",
       "      <th>3</th>\n",
       "      <td>4.806077</td>\n",
       "      <td>True</td>\n",
       "      <td>19</td>\n",
       "      <td>1</td>\n",
       "      <td>34</td>\n",
       "      <td>8904940584331855459</td>\n",
       "    </tr>\n",
       "    <tr>\n",
       "      <th>4</th>\n",
       "      <td>4.812691</td>\n",
       "      <td>True</td>\n",
       "      <td>22</td>\n",
       "      <td>3</td>\n",
       "      <td>34</td>\n",
       "      <td>-2126480030009879160</td>\n",
       "    </tr>\n",
       "  </tbody>\n",
       "</table>\n",
       "</div>"
      ],
      "text/plain": [
       "   weight_pounds  is_male  mother_age  plurality  gestation_weeks  \\\n",
       "0       3.562670     True          25          1               30   \n",
       "1       3.999185    False          30          1               32   \n",
       "2       7.438397     True          13          1               34   \n",
       "3       4.806077     True          19          1               34   \n",
       "4       4.812691     True          22          3               34   \n",
       "\n",
       "             hashmonth  \n",
       "0 -1403073183891835564  \n",
       "1 -7146494315947640619  \n",
       "2 -7146494315947640619  \n",
       "3  8904940584331855459  \n",
       "4 -2126480030009879160  "
      ]
     },
     "execution_count": 8,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "import google.datalab.bigquery as bq\n",
    "df = bq.Query(query + \" LIMIT 100\").execute().result().to_dataframe()\n",
    "df.head()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Let's write a query to find the unique values for each of the columns and the count of those values."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {},
   "outputs": [],
   "source": [
    "def get_distinct_values(column_name):\n",
    "    sql = \"\"\"\n",
    "SELECT\n",
    "  {0},\n",
    "  COUNT(1) AS num_babies,\n",
    "  AVG(weight_pounds) AS avg_wt\n",
    "FROM\n",
    "  publicdata.samples.natality\n",
    "WHERE\n",
    "  year > 2000\n",
    "GROUP BY\n",
    "  {0}\n",
    "    \"\"\".format(column_name)\n",
    "    return bq.Query(sql).execute().result().to_dataframe()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f29988a8210>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2999da0a10>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "df = get_distinct_values('is_male')\n",
    "df.plot(x='is_male', y='num_babies', kind='bar');\n",
    "df.plot(x='is_male', y='avg_wt', kind='bar');"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2998a86a10>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2999de0150>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "df = get_distinct_values('mother_age')\n",
    "df = df.sort_values('mother_age')\n",
    "df.plot(x='mother_age', y='num_babies');\n",
    "df.plot(x='mother_age', y='avg_wt');"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f299882e410>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2998705fd0>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "df = get_distinct_values('plurality')\n",
    "df = df.sort_values('plurality')\n",
    "df.plot(x='plurality', y='num_babies', logy=True, kind='bar');\n",
    "df.plot(x='plurality', y='avg_wt', kind='bar');"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2998733150>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "image/png": "iVBORw0KGgoAAAANSUhEUgAAAWoAAAETCAYAAAAf9UzqAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAADl0RVh0U29mdHdhcmUAbWF0cGxvdGxpYiB2ZXJzaW9uIDIuMS4yLCBodHRwOi8vbWF0cGxvdGxpYi5vcmcvNQv5yAAAIABJREFUeJzt3XmcneP9//HXyCBCwtR3bEETbedjF0mEUorQn720ltDYYqtdKbV9RYv+LLWENkWpqLUVsbSWWmOp2pfQ8KHWBmFao0IQSeb7x3WfzJ0zZ+ZcZ+bcM/fMvJ+PRx6Zuc/nfO7rPveZz7nu+1z3ddc0NzcjIiL5tUh3N0BERNqnQi0iknMq1CIiOadCLSKScyrUIiI5V5tF0sbGWa2GktTVDaCpaXbZ58bGKWd1c/a27VFOvT96Ws76+oE1bcV3WY+6trZfVeOUs7o5e9v2KKfeH70lJ0T2qM3sJ8CBQDPwIrC/u39R0ZpERKRDyvaozWwwcBQw0t3XBvoBY7JumIiIBLGnPmqBJcysFhgAvJddk0REJK0m5hJyMzsaOAv4HLjH3X/UXvzcufOaKz0HIyLSx7X5ZWLZQm1mdcDNwB7Ax8BNwGR3v7at55Qa9VFfP5DGxlllWxobp5zVzdnbtkc59f7oaTk7O+pjK+BNd29096+AKcDGEc8TEZEqiBn18Q6wkZkNIJz6GA08nWmrRERkgbI9and/ApgMPEsYmrcIcHnG7RIRkUTUOGp3Hw+Mr+aK9xjf1MYjbS1vP/aPP6/rVHuydN999zFoUD1Dh67W3U0RkR4ok0vIZWH33Xcfw4dvqEItvdbCHa+e0YHqSfrUpEwnnXQc48aNZezY3bnttinccstkJk6csODxO+/8M2eccQYAkyZdwV57/ZBjjjmM8eNP5vrrrymZs6npI8aNGwvAa6+9yne+M5KZM2cCsPvu3+fFF1/ggQceYOLEi9lvv714990ZGW+liPQ2fapHfdJJpzFo0NJ8+eUXHHjgPkyY8FsOPfQADjvsaADuv/9ejjrqcF55ZTpTpz7AVVddx7x58xg3bixma5TMWVf3NebMmcNnn33KtGnPsfrqazJt2nPAMOrqvsY666zHlltuyfDhG7LFFlt14daKdF5LT1m95O7Upwr1TTfdyMMPTwXgww8/4L333mOllQbz0ksvssoqq/DOO28zYsQIJk68nE03/S6LL94fgE022bTdvOussy7Tpr3A888/x957788TTzxGc3Mz6603LOtNEulxVPwr12cK9bPPPs3TTz/JZZddRf/+/TniiIOZM+dLRo/emgcfvJdVVx3CZpttTk1NDZXe8HfddYcxbdrzzJz5Pptu+l2uu+5qampq2Hjj9gu8iEiMPlOoP/vsUwYOHET//v15++23mD79JQA222xLrr76KlZYwTn00COBUHjPO++XjB27H/PmzeOxxx5lxx13aTP3sGHD+d3vfsuwYcNZZJFFGDRoEH//+9845JAjAFhyySWZPTtuPlsRCUp9QdlWzzu2l15JzjzptkLd1ouTxeWaABtuuDG33jqFffcdwyqrfJ0111wbgEGDBjF06FDefPPNBcvWWGMtNtlkM/bbb09WWGFFVl99TZZaaqk2c6+44koArLfe+kAo9I2NHzJo0CAAtttuO04++RQmT76RM888l8GDV45qs4h0nzydoukzPerFFluM88+/uORj5557Uatle+65NwcccAhffPEFhx9+EGPGjG03/5Qpdyz4eZ99xrHPPuMW/D5ixAiuvfamDrZcpLo0lK66uqKX3mcKdaXOPfcs3nrrTebM+ZJtt90Bs9W7u0ki0kepULfh9NPParXs/PPP4cUXXwCgtnYR5s6dz267jWH77Xfq6uaJSB+iQl2B44772YKfKzk/LiLSGX3qykQRkZ5IhVpEJOdUqEVEck7nqEV6iZ56MYeUpx61iEjOqVCLiORc2VMfZmbAH1OLVgNOc/fWl/OJiEibOnpZetlC7e4ODAMws37Au8AtHWmkiIhUrtJTH6OB19397SwaIyIirVU66mMMcEO5oLq6AdTW9mu1vL5+YNRKYuOUs7o5e9v29L2crW8MXTq+9A2kY2O7M2fb29/bci4sulCb2WLATsBJ5WKbmlrPvRx7yXUW05wqZ77XrZzVz1lQSXxsbHfm7G3bk45tr2BXcupjW+BZd/+ggueIiEgnVVKo9yTitIeIiFRXVKE2swHA1sCUbJsjIiLFos5Ru/tsYNmM2yIiRXQ3FgFdmSgiknsq1CIiOadCLSKScyrUIiI5p0ItIpJzKtQiIjmnQi0iknMq1CIiOadCLSKSc7q5rUg30I1opRLqUYuI5JwKtYhIzqlQi4jknAq1iEjOqVCLiOScCrWISM6pUIuI5JwKtYhIzkVd8GJmywBXAGsDzcA4d/97lg0TEZEg9srECcDd7r6rmS0GDMiwTSI9VssVh7q/oVRP2UJtZoOAzYD9ANx9DjAn22aJiEhBTI96NaARuMrM1gOeAY5298/aekJd3QBqa/u1Wl5fPzCqUbFxylndnL1te7onZ1OrJaXjOx7Xl3O2/dr3tpwLiynUtcBw4Eh3f8LMJgAnAv/b1hOammaXbExj46yyK4uNU87q5uxt29PdOdNi4yvJ21dz9rbtSce2V7BjRn3MAGa4+xPJ75MJhVtERLpA2ULt7jOBf5mZJYtGA9MzbZWIiCwQO+rjSOC6ZMTHG8D+2TVJRETSogq1uz8PjMy4LSIiUoKuTBQRyTkVahGRnNM9E0XK0P0NpbupRy0iknMq1CIiOadCLSKScyrUIiI5p0ItIpJzKtQiIjmnQi0iknMq1CIiOadCLSKScyrUIiI5p0vIpc/SjWilp1CPWkQk51SoRURyToVaRCTnVKhFRHIu6stEM3sLmAXMA+a6u27LJSLSRSoZ9bGFu/87s5aIiEhJOvUhIpJzsT3qZuAeM2sGLnP3y9sLrqsbQG1tv1bL6+sHRq0sNk45q5uzt21P+dimVktKx8fGZZGzdVxfztl1r3t351xYbKHexN3fM7PlgHvN7BV3f7it4Kam2SUb09g4q+yKYuOUs7o5e9v2VBpbEBtfSV7l7B3rzjpnewU7qlC7+3vJ/x+a2S3AKKDNQi3SXXQjWumNyp6jNrMlzWxg4Wfge8BLWTdMRESCmB718sAtZlaIv97d7860VSIiskDZQu3ubwDrdUFbRESkBA3PExHJORVqEZGcU6EWEck5FWoRkZxToRYRyTkVahGRnFOhFhHJOd3cVnoE3YhW+jL1qEVEck6FWkQk51SoRURyToVaRCTnVKhFRHJOhVpEJOdUqEVEck7jqKXb6LZZInHUoxYRybnoHrWZ9QOeBt519x2ya5KIiKRV0qM+Gng5q4aIiEhpUYXazFYGtgeuyLY5IiJSLPbUx0XACcDAmOC6ugHU1vZrtby+Purp0XHKWd2cXb/uplZL2o6Pje1tOVvH9eWcPXtfVhrbomyhNrMdgA/d/Rkz27xsRqCpaXbJxjQ2zir73Ng45axuzu7enoJK4mNjlbP35Oxt25OOba9gx5z62ATYyczeAm4EtjSza6NbISIinVK2R+3uJwEnASQ96p+6+9iM2yUiIgmNoxYRybmKrkx096nA1ExaIiIiJekScqk63TZLpLp06kNEJOdUqEVEck6FWkQk51SoRURyToVaRCTnVKhFRHJOhVpEJOdUqEVEck6FWkQk51SoRURyTpeQS5RSdwwHXRou0hXUoxYRyTkVahGRnFOhFhHJORVqEZGcU6EWEck5FWoRkZwrOzzPzPoDDwOLJ/GT3X181g0TEZEgpkf9JbClu68HDAO2MbONsm2WiIgUlO1Ru3sz8Gny66LJv+YsGyUiIi2irkw0s37AM8A3gd+4+xPtxdfVDaC2tl+r5fX1A6MaFRunnNXN2X5cU8mlpZ/TOrZzcX05Z9e87j0lZ8/el5XGtogq1O4+DxhmZssAt5jZ2u7+UlvxTU2zSzamsXFW2XXFxilndXNWsu602OdUO045+2bO3rY96dj2CnZFoz7c/WNgKrBNJc8TEZGOK1uozaw+6UljZksAWwGvZN0wEREJYk59rAhcnZynXgT4k7v/JdtmiYhIQcyoj2nA+l3QFhERKUFXJoqI5JwKtYhIzqlQi4jknAq1iEjOqVCLiOScCrWISM7pLuR9XMvdxXVncZG8Uo9aRCTnVKhFRHJOhVpEJOdUqEVEck6FWkQk51SoRURyTsPzeqGWIXegYXciPZ961CIiOadCLSKScyrUIiI5V/YctZmtAvwBWAGYD1zu7hOybpiIiAQxPeq5wHHuvgawEXC4ma2ZbbNERKQg5p6J7wPvJz/PMrOXgcHA9IzbJkVKjebQSA6R3q+i4XlmNoRwo9sn2ourqxtAbW2/Vsvr6wdGrSc2ru/lbGq1pHR867hKYrszZ9vb31dz9tx9mUXOnr0vK41tEV2ozWwp4GbgGHf/pL3YpqbZJRvT2Dir7Hpi4/p6zoJK4mNjuzNnb9se5dT7Iza2vYIdNerDzBYlFOnr3H1KdAtERKTTyhZqM6sBrgRedvcLsm+SiIikxZz62ATYG3jRzJ5Plp3s7ndm1ywRESmIGfXxKFDTBW0REZESNClTN9MESiJSji4hFxHJORVqEZGcU6EWEck5FWoRkZxToRYRyTkVahGRnFOhFhHJORVqEZGcU6EWEck5FWoRkZzTJeQZ0d1YRKRa1KMWEck5FWoRkZxToRYRyTmdo65Qy7lnTUkqIl1DPWoRkZxToRYRybmypz7M7PfADsCH7r529k3qehpKJyJ5FtOjngRsk3E7RESkDWULtbs/DHzUBW0REZESMhn1UVc3gNrafq2W19cPjHp+bFy52C0Peyf5qeXUxgMTVy0R2dRqSdt5Y2M7HteXc3bd695TcvbcfZlFzp69LyuNbZFJoW5qmg0Un/sNyp37ra8fSGPjrKj1VBJbEBtfSV7l7B3rVs785+xt25OOba9ga9SHiEjO5eaCF11IIiJSWtketZndAPw9/GgzzOyA7JslIiIFZXvU7r5nVzQklsY8i0hfo3PUIiI5p0ItIpJzKtQiIjmnQi0iknMq1CIiOadCLSKScyrUIiI5p0ItIpJzKtQiIjmnQi0iknMq1CIiOadCLSKScyrUIiI5p0ItIpJzKtQiIjmnQi0iknMq1CIiOadCLSKSc1E3tzWzbYAJQD/gCnc/O9NWiYjIAjE3t+0H/AbYFlgT2NPM1sy6YSIiEsSc+hgF/NPd33D3OcCNwPezbZaIiBTUNDc3txtgZrsC27j7gcnvewMbuvsRXdA+EZE+L6ZHXVNiWfvVXUREqiamUM8AVkn9vjLwXjbNERGRYjGjPp4CvmVmQ4F3gTHAXpm2SkREFijbo3b3ucARwF+Bl4E/ufs/sm6YiIgEZb9MFBGR7qUrE0VEck6FWkQk51SoRURyToVaRCTnoiZl6mnMbGlgG2Aw4eKc94C/uvvHRXGrEy6HT8fd7u4vl8gZFRu77hy0s5KcWbSzhjA9QTr2SXdvLoqLXXclr3vsuqPiMmxnbM4s2lnV/ZPh9nRnO6NzdlZmPWozW93MfmZmF5vZhOTnNUrELW1me5jZsWb2k+TnZTqa08z2AZ4FNgcGAEsCWwDPJI8V4n5GmLekBniSMF68BrjBzE4syhkVG7vuHLSzkpxZtPN7wGvA6cB2wPbAz4HXkscqXXclr3vsuqPiMmxnbM4s2lnV/ZPh9nRnO6Nzpp7zAzN7zcz+a2afmNksM/ukVGyxTHrUyR/tnoQ/3CeTxSsT/mhvLEyTmmzQeOAewsU0EDb2l2b2c3f/Q6U5gVOAESU+/eqAJ4BCzgOAtdz9q6K4C4B/AOmpXGNjY9fd3e2sJGcW7ZwAbOXubxXFDgXuBAofvrHrruR1j113bFxW7YyNzaKd1d4/WW1Pd7azkpwF5wI7ljrCLCerUx9ZFLbYnDWUnotkPgvPWzIfWAl4uyhuxeSx4ufGxMauu7vbWUnOLNpZS5iaoNi7wKIdWHclr3vsumPjsmpnbGwW7az2/sli3d3dzkpyFnzQkSIN2RXqLApbbM6zgGfN7B7gX8myVYGtgTNScccA95vZa0Vx3yRciUkHYmPX3d3trCRnFu38PfCUmd2Yil2FMD3BlR1YdyWve+y6Y+OyamdsbBbtrPb+yWp7urOdleQseNrM/gjcCnxZWOjuU9qIXyCTKxMt3BHm14TzR63+aN397iRuX+A0wqmPVhvr7pMqzZnE1gH/j3CSv4bwqftXd28qaucitHwRUYh7yt3nldimqNjYdeegnZXkzKKda9DyxWMh9nZ3n97BdVfyuseuOyouw3bG5syinVXdPxluT3e2MzpnEn9VicXN7j6uVHxaZpeQZ1TYoguBiEiv0dzc3Gf+NTQ0XB4Z95cKckbFxq47B+2sJGcW7Ty9yuuu5HWPXXdUXIbtjM2ZRTurun8y3J7ubGfJuIaGhv4NDQ2HNzQ0TGxoaPh94V9Mzi6/4MXM/hIZd3m1cwKXRcYdFLvuCmJj111JbBbtrCRnFu18psrrruR1j113bFwl68/i/ZFFO6u9f7JYdyWxWbSzrbhrgBUIZxAeIoxamxWVMfbTpFr/GhoaVoyMG1HtnHn/19DQsFwGOZft7u3SP/3Tv2YaGhqeS/6flvy/aENDwwMxz+1105xauFroJGBnoD5Z/CFwG3B2zFVDZnaXu2+b+n1QknNl4C53vz712ER3Pyz5eQXCuPD5hC9JjwR+SJjH+2h3fz/1vK8VrbaG0AtYH6hx94+SuG1SX74uDVwAbAC8BPzE3T9I5Twb+JW7/9vMRgJ/StqyKLCPuz+UxD0LTAFucPfXy7wWI4HzCEOeTiJ80z4KeBU42N2fS+KWAk5ItndlYA7wOnBp+kvhJLaWMNxyF8JInsJVXbcBVxYPwWyjXZe7+8HJz/2AA5P13u3uf0vFneruZ6Z+H0AYhdIMXEIYIfAD4BXgF+7+aTvrfNXdG0osX9fdpyU/Lwr8LHmNXgLOdPfZyWNHADcm++ebhNdyXcCBA939xVTOKYR9dGuZNq0GnEp4/c4GLgS+TXjPHZ8eY5x8x7MfLftoLuHL+UvdfWoqrqr7J/k9ah91Zv8kz2+1j2L3T/J41D6K3T9F7XjS3UeZ2cPAYcBMwlWUq5V7blYXvEQVgtgikMTGFoI/AQ8Am7v7zOS5KwD7AjcRRpRgZsPbaFYNMKxo2VWEN/TNwDgz+yGwl7t/CWyUipsE3EG4SulB4DrC1VLfBy5l4bu3/5vWQw0HE652agYKO++XQGFEy/nA+8COhDfvZYQPpILt3b1wFeB5wB7u/pSZNQDXAyOTx+qAZYAHzWwmcAPwR3cvdYu1iYQPn2WAxwgfDlub2ejksW8ncdcBtxAO63ZPXoMbgVPNrMHdT07lvAb4mHBFWWEc7MqEfXQtsAeU/DArqCFciVZwGeHqsCeBi83sIXc/NnnsB8CZqdhJhFFDSxD21cvArwiv6W+BvZN1z6Jl6GhhqOiAwnJ3H1SUs/B+OhtYlrCvdibs98KVaoe6+6+TnycAF7r7LWa2eRK3SSrnhoQP2YvN7D7CPrrD3ecUvRaTkseWBh4nvFd/AXyP8Pe0ZSr2SsJ77v8DuwKfAI8Q9tE67n5JElft/QPx+2gSEfsnWX/sPppE3P6B+H0Uu3/SLk8GT5wK3A4sBfxvO/ELZDWOOrYQxBYBiC8EQ9z9nPRKkoJ9jpmlh8E8RThPVGpwevEl7N9w9x8mP99qZqcAD5jZTkVxyxfe7GZ2WKodl5jZAUWxJwBbEXo9hU/pN919aIn2FIx098KHyIXJ8Ma0Rc2s1sNdeZZw96cA3P1VM1s8Fdfk7j8FfmpmmxKu+HzWzF4mfLimvx9Y1N3vStp3jrtPTnLeb2a/SsUNSX1gXmBmT7n7GWa2PzAdSBfq4e5uRW2fATxuZq+mljUSCkt6HzUnvy+XWjbK3ddN2vhrYGLS49mT1vu3wd13tzBHxPuEK9uazewR4IVU3CRC8Tu+cNTSzv5Jr2M0sIG7f5X0nNI5039vy7n7LQDuPtXMBhbl/NDdd02W70w4z3958n3MDe5+TxI30N1/m7TvMHc/P1l+ZdI7TBvh7vsnPz9qZo+7+2lJO58n9GCh+vsH4vdR7P6B+H0Uu38gfh/F7p+0awgdzSHA1cmy5UvEtZJVoY4tBLFFAOILwdtmdgJwdWrnLU845PtXKt/LwCHu/lpx483sX0WLFjezRdx9ftK+s8xsBvAw4VOxIP3lbPElpP3Sv7j7rywM1L8wWd94Sl/8s5yZHUt4sw0ysxpvmXCm+Mvg3wB3JqdA7jaziwhHNqMJf4ituPsjwCNmdiThaGMPIF2ov7Awb8LSQLOZ7ezut5rZd4H0sMjPzOw77v6ome0IfJTkn5/80aU1mdluwM2F1zQ5LN8NSA/LfAMY7e7vFLe7aB8tltqeucDBZjaecGS1VPFzk7hmM7uz8FomvzenHj/SzEYQpii4lTCGv63zhEub2Q8I+2jxwqmB4pzAZDObROjx3mJmx9Cyf4q3sdCuWYQ/8GuSHuzuwImEaw8A5idHTMsQepMj3f3p5LC9X1HOr8zsG+7+enJEOSdZx5dF7az2/oEK91G5/ZMsi91HS5vZLoS/l/b2D8Tvo9j9k3Yb8F/CKc4vSzzepsxHfbj7Ix7O4Q4GzmHhXvIXZva95E3RbGY7A5QoApAUguTxhQoBC39i7kE4tHnIzJrM7CNgKlB4EQtOp+3tP7Lo9z+z8CEk7n41cBzJmz1xm4VTNLj7qYWFyR+NF6/E3We4+26E0yT3Eg4Ni/0OGEh4M18N/E+ScwWKim/Sm/8lcAjhNMtowpvmXSB9NJHuFRWeO8/d7071uAp+nGznOMLRzBZm9jHhiOeoVNyhhA/QjwnnAI9K2llP+ABJG0M49J5pZq8mvbSZhEPgMam4iwhHZ6Wcm/r5aQsXRKW35+eE0wBDip73dGofLXhNzOwbFH0D7+7PEI56IBx99W+jLQ8RDs13IPQ6l09yrkA4xVXIdwrhvXgDcCzhCra7gW8BPyrK2eq8p7t/5O6Xunv6vXgC4f15NaFnd5KFq0Mfo/Vh9fGEo9xXCafxjk/aWQ+kR04V9s8Hyf55jc7tH4jfR9H7J4mJ2UcPAztRZv8k+U5J8pTbR7H7J21ld9/D3c919/ML/9qIXUhWVybe6O5jIuLWI+zQ+cBPCH/s+xIKy0Hu/lgqdl3gCqCB8CXAuOSQvh7Y090vTsWuTjin9rinTvRb6ou5VNxg4In24srEbls4KuhMTsIH0zfc/aWM2tmZnGsQvlQql3ONJGe7r3uybENCr+R1wuQ5GwHT3f3OorhRhPONT5nZmoRpJV/paFw7sQ4s6MGViNuUMGHY023k3BCYX2E710riXq6gnaVypte9FrBtqdcyif02MDfmdUrilyV0hC5y97GlYori/+DuJWeP62hsIa7oaLJU3IrAS+6+bJXbeY277x0R125OC0OOL/HUl8axunzUh5nt7+6lLqXsUFxxrJkdBRxOOLUxjDDa4rbksWfdfXglccnvRxK+iS6XMyquwnbmIedhhG/dy72eZeOS38cTikkt4UhiFKEXsxXhqtSz2ojbkNAj7VBcJ3OWbGMnt6eSnF3ZzttpbUvCaQrcfac24moIH2YLxVUS28mcse0sGdfJnG22M5V7OmHKizcJpz5qCB/E65ZY50K648YBhcOdasUVxx5E+NLkUzMbQjjnNMTdJ7DwKZLYOICDI2Nj4ypZfx5yjox8PWPiIBxWDwMWJxxSr+zun5jZeYSji7MyilPOuNiVCd/7XEHLl4MbEEZKpK1CmLkyHTeyRFwlsZXk7Ew7S8Vlte0F27bzWLuyGp43rY2Hakh9yxkbV2Fsv8Jht7u/ZWFYzWQz+zoLF4zYOOWsfs65HuZnmW1mr7v7J8nzPjez+RnGKWdc7EjgaMI0xMe7+/Nm9rkn4/BTRkTGVRJbSc4s2plFTgDcvXg4brSsvkxcnjA2cccS//7TgbhKYmea2YJx0Enx2IHwJdw6HYhTzurnnGPhwgYIb3gALFzQMz/DOOWMiHX3+e5+IbA/cIqF4XStOnWxcX09ZzVklfgvwFLu3mpImJlN7UBcJbH7EK64WsDDcKB9zOyyDsQpZ/VzbubhYqHCqJ2CRQlfJmcVp5zxsbj7DGA3M9uecHFMSbFxfT1nZ/S6S8hFRHqbLp89T0REKqNCLSKScyrUIiI5p0It3c7MhpnZ7uUjwcyGmNnBRcvutHCJcY9hZlPNbIfubof0DCrUkgfDWHgelvYMIVyws4C7b+dl5tUW6cm648pE6SUszMt9FvA5Ya7vswgTSK1FmPe3MB/wae5+h5ktR5gXu3CB0n2EeYh/QZgZ8HngYXc/ysyuA4xwFd0/CXO7NBEmeBqaxP7Tw1STbwE7eJgn5ZuEuY/rCcMFT/aWGy80Ey5Q2IUwcdfx7n5zO9v3LrC+u39oZncSLvfdPtmO59x9sJktlmz3dwkzxL1ImNP4Uws3nLiAMPF8f8LkW8d66xs8jyFMfLULsCphFrhFCMPmznT3G8rvDenN1KOWDkmK1eXAju6+PqFYQ5hu81LCjRVGEC56uczMliHMPva2u6/j7usQ7tjxH8LdcO5z92HuXpiR72h3H5nE/YMwIx+EuUymJ7G7lmjadcD1HuZPGAtca2HiroJP3H0DwgT0F5d4ftqDwJYW7goyBFgt+Xk0yZwOhNnr/uvuozzMFf4e4SYYEIr0Q+4+inDUsBwLz2KIhSl5DyTMuzwj2c4Lk1xrA3chfZ561NJRGwHPest83r8nFKbhwFDgLrMFc883EyajeRw41sLcEg8Bf20n/z5m9iNCL3VJSkzNWszCJO7DSOZ9cffpSc97I8JUoBBuNkHSlpXMrL+7f9FGygcIExa9S5gLo4YwOdJWwP1JzE6Eo4HCh8bitExGvxMwysyOS34fQMsdUyBMtfsOsJ233BnkQcJUpV8H7nX3J8ptt/R+KtTSUTWUnqS9Bpjm7puVelJymfnWhB7ticB3SsRsSpjydmN3bzSzvSg6L91Om0pJt/MLCPNvJx8k7f1xkwyJAAAB0klEQVQN3E+Y03lG8nMNoTc9mjARWGGdh7n7AyWeXwPs7O5vtJH/ccJr8XXCrd5w94vM7M+ED4NLzOweT81tLn2TTn1IRz0OjEjOCUO4gw6Eez5+y8y2KASa2QZmVmNmQwmnHm4kTMo+wsKdQz4h3EGmYBnCnTD+Y+EWYunTBcWxC3iYZOh5ksuhLcy5vR6hN1yxZBKdeUm++wnn1PcDvvKWu5rcTjhKWCJZ50AL83IXHjvRwo1dMbP/SV6DgrsJH0h3WphHGgu3lXvd3S8j3LNvVEfaLr2LCrV0iIfbnP0YuMPM/ka4GelXhNMEOwHjzewFC7dfO53Qu9wceC45HXEX8ONkzon7gSWT+IuTx14nzG19F6H4F0wD3MxeMrPJJZr2I2CshdkWrwf2dvfGTmzq/cBsd3/fw13kP6fl/DSEL01fAJ5K1vko4UYIAMcQCv0LZvYioTAPTidPeuL7AbdbuD3WUWb2DzN7jnCnoVM60XbpJTTXh3SYmQ30cM84LNy78gB3b3UqQ0Q6R+eopTOOsnC/y1rCPSwP6ub2iPRK6lFLn5YMMyx1x+gp7v6Lrm6PSCkq1CIiOacvE0VEck6FWkQk51SoRURyToVaRCTn/g+DEhtT8VryIAAAAABJRU5ErkJggg==\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f2998b70310>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "df = get_distinct_values('gestation_weeks')\n",
    "df = df.sort_values('gestation_weeks')\n",
    "df.plot(x='gestation_weeks', y='num_babies', logy=True, kind='bar', color='royalblue');\n",
    "df.plot(x='gestation_weeks', y='avg_wt', kind='bar', color='royalblue');"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "All these factors seem to play a part in the baby's weight.  Male babies are heavier on average than female babies. Teenaged and older moms tend to have lower-weight babies.  Twins, triplets, etc. are lower weight than single births.  Preemies weigh in lower as do babies born to single moms. In addition, it is important to check whether you have enough data (number of babies) for each input value. Otherwise, the model prediction against input values that doesn't have enough data may not be reliable.\n",
    "<p>\n",
    "In the rest of this notebook, we will use machine learning to combine all of these factors to come up with a prediction of a baby's weight."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h2> Creating a ML dataset using Dataflow </h2>\n",
    "<p>\n",
    "I'm going to use Cloud Dataflow to read in the BigQuery data, do some preprocessing, and write it out as CSV files. \n",
    "\n",
    "Instead of using Beam/Dataflow, I had three other options:\n",
    "<ol>\n",
    "<li> Use Cloud Dataprep to visually author a Dataflow pipeline. Cloud Dataprep also allows me to explore the data, so we could have avoided much of the handcoding of Python/Seaborn calls above as well!\n",
    "<li> Read from BigQuery directly using TensorFlow. \n",
    "<li> Use the BigQuery console (http://bigquery.cloud.google.com) to run a Query and save the result as a CSV file. For larger datasets, you may have to select the option to \"allow large results\" and save the result into a CSV file on Google Cloud Storage.\n",
    "</ol>\n",
    "<p>\n",
    "\n",
    "However, in this case, I want to do some preprocessing. I want to modify the data such that we can simulate what is known if no ultrasound has been performed. If I didn't need preprocessing, I could have used the web console. Also, I prefer to script it out rather than run queries on the user interface. Therefore, I am using Cloud Dataflow for the preprocessing."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {},
   "outputs": [
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "/usr/local/envs/py2env/lib/python2.7/site-packages/oauth2client/contrib/gce.py:99: UserWarning: You have requested explicit scopes to be used with a GCE service account.\n",
      "Using this argument will have no effect on the actual scopes for tokens\n",
      "requested. These scopes are set at VM instance creation time and\n",
      "can't be overridden in the request.\n",
      "\n",
      "  warnings.warn(_SCOPES_WARNING)\n"
     ]
    }
   ],
   "source": [
    "import apache_beam as beam\n",
    "import datetime\n",
    "\n",
    "def to_csv(rowdict):\n",
    "    # pull columns from BQ and create a line\n",
    "    import hashlib\n",
    "    import copy\n",
    "    CSV_COLUMNS = 'weight_pounds,is_male,mother_age,plurality,gestation_weeks'.split(',')\n",
    "    \n",
    "    # create synthetic data where we assume that no ultrasound has been performed\n",
    "    # and so we don't know sex of the baby. Let's assume that we can tell the difference\n",
    "    # between single and multiple, but that the errors rates in determining exact number\n",
    "    # is difficult in the absence of an ultrasound.\n",
    "    no_ultrasound = copy.deepcopy(rowdict)\n",
    "    w_ultrasound = copy.deepcopy(rowdict)\n",
    "\n",
    "    no_ultrasound['is_male'] = 'Unknown'\n",
    "    if rowdict['plurality'] > 1:\n",
    "      no_ultrasound['plurality'] = 'Multiple(2+)'\n",
    "    else:\n",
    "      no_ultrasound['plurality'] = 'Single(1)'\n",
    "      \n",
    "    # Change the plurality column to strings\n",
    "    w_ultrasound['plurality'] = ['Single(1)', 'Twins(2)', 'Triplets(3)', 'Quadruplets(4)', 'Quintuplets(5)'][rowdict['plurality']-1]\n",
    "    \n",
    "    # Write out two rows for each input row, one with ultrasound and one without\n",
    "    for result in [no_ultrasound, w_ultrasound]:\n",
    "      data = ','.join([str(result[k]) if k in result else 'None' for k in CSV_COLUMNS])\n",
    "      key = hashlib.sha224(data).hexdigest()  # hash the columns to form a key\n",
    "      yield str('{},{}'.format(data, key))\n",
    "  \n",
    "def preprocess(in_test_mode):\n",
    "    job_name = 'preprocess-babyweight-features' + '-' + datetime.datetime.now().strftime('%y%m%d-%H%M%S')\n",
    "    \n",
    "    if in_test_mode:\n",
    "        OUTPUT_DIR = './preproc'\n",
    "    else:\n",
    "        OUTPUT_DIR = 'gs://{0}/babyweight/preproc/'.format(BUCKET)\n",
    "    \n",
    "    options = {\n",
    "        'staging_location': os.path.join(OUTPUT_DIR, 'tmp', 'staging'),\n",
    "        'temp_location': os.path.join(OUTPUT_DIR, 'tmp'),\n",
    "        'job_name': job_name,\n",
    "        'project': PROJECT,\n",
    "        'teardown_policy': 'TEARDOWN_ALWAYS',\n",
    "        'max_num_workers': 3,   # CHANGE THIS IF YOU HAVE MORE QUOTA\n",
    "        'no_save_main_session': True\n",
    "    }\n",
    "    opts = beam.pipeline.PipelineOptions(flags=[], **options)\n",
    "    if in_test_mode:\n",
    "        RUNNER = 'DirectRunner'\n",
    "    else:\n",
    "        RUNNER = 'DataflowRunner'\n",
    "    p = beam.Pipeline(RUNNER, options=opts)\n",
    "    query = \"\"\"\n",
    "SELECT\n",
    "  weight_pounds,\n",
    "  is_male,\n",
    "  mother_age,\n",
    "  plurality,\n",
    "  gestation_weeks,\n",
    "  FARM_FINGERPRINT(CONCAT(CAST(YEAR AS STRING), CAST(month AS STRING))) AS hashmonth\n",
    "FROM\n",
    "  publicdata.samples.natality\n",
    "WHERE year > 2000\n",
    "AND weight_pounds > 0\n",
    "AND mother_age > 0\n",
    "AND plurality > 0\n",
    "AND gestation_weeks > 0\n",
    "AND month > 0\n",
    "    \"\"\"\n",
    "  \n",
    "    if in_test_mode:\n",
    "        query = query + ' LIMIT 100' \n",
    "  \n",
    "    for step in ['train', 'eval']:\n",
    "        if step == 'train':\n",
    "            selquery = 'SELECT * FROM ({}) WHERE ABS(MOD(hashmonth, 4)) < 3'.format(query)\n",
    "        else:\n",
    "            selquery = 'SELECT * FROM ({}) WHERE ABS(MOD(hashmonth, 4)) = 3'.format(query)\n",
    "\n",
    "        (p \n",
    "         | '{}_read'.format(step) >> beam.io.Read(beam.io.BigQuerySource(query=selquery, use_standard_sql=True))\n",
    "         | '{}_csv'.format(step) >> beam.FlatMap(to_csv)\n",
    "         | '{}_out'.format(step) >> beam.io.Write(beam.io.WriteToText(os.path.join(OUTPUT_DIR, '{}.csv'.format(step))))\n",
    "        )\n",
    " \n",
    "    job = p.run()\n",
    "  \n",
    "preprocess(in_test_mode=False)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "You may get a warning about access scopes. It's safe to ignore this.\n",
    "\n",
    "Note that after you launch this, the actual processing is happening on the Cloud. Go to the GCP web console to the Dataflow section and monitor the running job. You'll see a job that's running. If you click it, you should get a screen like this. It took about <b>55 minutes</b> for me.\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<img src=\"dataflow.png\" width=\"500\"/>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Once the job has completed, run the cell below to check the location of the are processed files."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "gs://cloud-training-demos-ml/babyweight/preproc/eval.csv-00000-of-00006\n",
      "gs://cloud-training-demos-ml/babyweight/preproc/train.csv-00000-of-00015\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "gcloud storage ls gs://${BUCKET}/babyweight/preproc/*-00000*"   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h1>Part 2: Developing a Machine Learning Model using TensorFlow and Cloud ML Engine</h1>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h2> Creating a TensorFlow model using the Estimator API </h2>\n",
    "<p>\n",
    "First, write an input_fn to read the data."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "/usr/local/envs/py2env/lib/python2.7/site-packages/h5py/__init__.py:36: FutureWarning: Conversion of the second argument of issubdtype from `float` to `np.floating` is deprecated. In future, it will be treated as `np.float64 == np.dtype(float).type`.\n",
      "  from ._conv import register_converters as _register_converters\n"
     ]
    }
   ],
   "source": [
    "import shutil\n",
    "import numpy as np\n",
    "import tensorflow as tf"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We may get a few warnings when we run this. Don't worry about them. "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {},
   "outputs": [],
   "source": [
    "CSV_COLUMNS = 'weight_pounds,is_male,mother_age,plurality,gestation_weeks,key'.split(',')\n",
    "LABEL_COLUMN = 'weight_pounds'\n",
    "KEY_COLUMN = 'key'\n",
    "DEFAULTS = [[0.0], ['null'], [0.0], ['null'], [0.0], ['nokey']]\n",
    "TRAIN_STEPS = 1000\n",
    "\n",
    "def read_dataset(prefix, pattern, batch_size=512):\n",
    "    # use prefix to create filename\n",
    "    filename = 'gs://{}/babyweight/preproc/{}*{}*'.format(BUCKET, prefix, pattern)\n",
    "    if prefix == 'train':\n",
    "        mode = tf.estimator.ModeKeys.TRAIN\n",
    "        num_epochs = None # indefinitely\n",
    "    else:\n",
    "        mode = tf.estimator.ModeKeys.EVAL\n",
    "        num_epochs = 1 # end-of-input after this\n",
    "    \n",
    "    # the actual input function passed to TensorFlow\n",
    "    def _input_fn():\n",
    "        # could be a path to one file or a file pattern.\n",
    "        input_file_names = tf.train.match_filenames_once(filename)\n",
    "        filename_queue = tf.train.string_input_producer(\n",
    "            input_file_names, shuffle=True, num_epochs=num_epochs)\n",
    " \n",
    "        # read CSV\n",
    "        reader = tf.TextLineReader()\n",
    "        _, value = reader.read_up_to(filename_queue, num_records=batch_size)\n",
    "        if mode == tf.estimator.ModeKeys.TRAIN:\n",
    "          value = tf.train.shuffle_batch([value], batch_size, capacity=10*batch_size, \n",
    "                                         min_after_dequeue=batch_size, enqueue_many=True, \n",
    "                                         allow_smaller_final_batch=False)\n",
    "        value_column = tf.expand_dims(value, -1)\n",
    "        columns = tf.decode_csv(value_column, record_defaults=DEFAULTS)\n",
    "        features = dict(zip(CSV_COLUMNS, columns))\n",
    "        features.pop(KEY_COLUMN)\n",
    "        label = features.pop(LABEL_COLUMN)\n",
    "        return features, label\n",
    "  \n",
    "    return _input_fn"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Next, define the feature columns."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [],
   "source": [
    "def get_wide_deep():\n",
    "    # define column types\n",
    "    is_male,mother_age,plurality,gestation_weeks = \\\n",
    "        [\\\n",
    "            tf.feature_column.categorical_column_with_vocabulary_list('is_male', \n",
    "                        ['True', 'False', 'Unknown']),\n",
    "            tf.feature_column.numeric_column('mother_age'),\n",
    "            tf.feature_column.categorical_column_with_vocabulary_list('plurality',\n",
    "                        ['Single(1)', 'Twins(2)', 'Triplets(3)',\n",
    "                         'Quadruplets(4)', 'Quintuplets(5)','Multiple(2+)']),\n",
    "            tf.feature_column.numeric_column('gestation_weeks')\n",
    "        ]\n",
    "\n",
    "    # discretize\n",
    "    age_buckets = tf.feature_column.bucketized_column(mother_age, \n",
    "                        boundaries=np.arange(15,45,1).tolist())\n",
    "    gestation_buckets = tf.feature_column.bucketized_column(gestation_weeks, \n",
    "                        boundaries=np.arange(17,47,1).tolist())\n",
    "      \n",
    "    # sparse columns are wide \n",
    "    wide = [is_male,\n",
    "            plurality,\n",
    "            age_buckets,\n",
    "            gestation_buckets]\n",
    "    \n",
    "    # feature cross all the wide columns and embed into a lower dimension\n",
    "    crossed = tf.feature_column.crossed_column(wide, hash_bucket_size=20000)\n",
    "    embed = tf.feature_column.embedding_column(crossed, 3)\n",
    "    \n",
    "    # continuous columns are deep\n",
    "    deep = [mother_age,\n",
    "            gestation_weeks,\n",
    "            embed]\n",
    "    return wide, deep"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "To predict with the TensorFlow model, we also need a serving input function. We will want all the inputs from our user."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {},
   "outputs": [],
   "source": [
    "def serving_input_fn():\n",
    "    feature_placeholders = {\n",
    "        'is_male': tf.placeholder(tf.string, [None]),\n",
    "        'mother_age': tf.placeholder(tf.float32, [None]),\n",
    "        'plurality': tf.placeholder(tf.string, [None]),\n",
    "        'gestation_weeks': tf.placeholder(tf.float32, [None])\n",
    "    }\n",
    "    features = {\n",
    "        key: tf.expand_dims(tensor, -1)\n",
    "        for key, tensor in feature_placeholders.items()\n",
    "    }\n",
    "    return tf.estimator.export.ServingInputReceiver(features, feature_placeholders)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Finally, train!"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "INFO:tensorflow:Using default config.\n",
      "INFO:tensorflow:Using config: {'_save_checkpoints_secs': 600, '_session_config': None, '_keep_checkpoint_max': 5, '_task_type': 'worker', '_is_chief': True, '_cluster_spec': <tensorflow.python.training.server_lib.ClusterSpec object at 0x7f421bb3f250>, '_save_checkpoints_steps': None, '_keep_checkpoint_every_n_hours': 10000, '_service': None, '_num_ps_replicas': 0, '_tf_random_seed': None, '_master': '', '_num_worker_replicas': 1, '_task_id': 0, '_log_step_count_steps': 100, '_model_dir': 'babyweight_trained', '_save_summary_steps': 100}\n",
      "INFO:tensorflow:Running training and evaluation locally (non-distributed).\n",
      "INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after 600 secs (eval_spec.throttle_secs) or training is finished.\n",
      "INFO:tensorflow:Create CheckpointSaverHook.\n",
      "INFO:tensorflow:Saving checkpoints for 1 into babyweight_trained/model.ckpt.\n",
      "INFO:tensorflow:loss = 16962.006, step = 1\n",
      "INFO:tensorflow:global_step/sec: 64.0398\n",
      "INFO:tensorflow:loss = 574.026, step = 101 (1.568 sec)\n",
      "INFO:tensorflow:global_step/sec: 84.4746\n",
      "INFO:tensorflow:loss = 605.14636, step = 201 (1.186 sec)\n",
      "INFO:tensorflow:global_step/sec: 84.3204\n",
      "INFO:tensorflow:loss = 680.4365, step = 301 (1.182 sec)\n",
      "INFO:tensorflow:global_step/sec: 82.045\n",
      "INFO:tensorflow:loss = 544.0405, step = 401 (1.221 sec)\n",
      "INFO:tensorflow:global_step/sec: 84.502\n",
      "INFO:tensorflow:loss = 585.97485, step = 501 (1.183 sec)\n",
      "INFO:tensorflow:global_step/sec: 85.934\n",
      "INFO:tensorflow:loss = 564.5591, step = 601 (1.162 sec)\n",
      "INFO:tensorflow:global_step/sec: 86.1974\n",
      "INFO:tensorflow:loss = 596.98096, step = 701 (1.160 sec)\n",
      "INFO:tensorflow:global_step/sec: 85.2933\n",
      "INFO:tensorflow:loss = 497.08707, step = 801 (1.174 sec)\n",
      "INFO:tensorflow:global_step/sec: 79.6788\n",
      "INFO:tensorflow:loss = 474.95947, step = 901 (1.258 sec)\n",
      "INFO:tensorflow:Saving checkpoints for 1000 into babyweight_trained/model.ckpt.\n",
      "INFO:tensorflow:Loss for final step: 619.3094.\n",
      "INFO:tensorflow:Starting evaluation at 2018-09-28-07:08:00\n",
      "INFO:tensorflow:Restoring parameters from babyweight_trained/model.ckpt-1000\n",
      "INFO:tensorflow:Finished evaluation at 2018-09-28-07:08:29\n",
      "INFO:tensorflow:Saving dict for global step 1000: average_loss = 1.1217324, global_step = 1000, loss = 574.27686\n",
      "INFO:tensorflow:Performing the final export in the end of training.\n",
      "INFO:tensorflow:Restoring parameters from babyweight_trained/model.ckpt-1000\n",
      "INFO:tensorflow:Assets added to graph.\n",
      "INFO:tensorflow:No assets to write.\n",
      "INFO:tensorflow:SavedModel written to: babyweight_trained/export/exporter/temp-1538118510/saved_model.pb\n"
     ]
    }
   ],
   "source": [
    "from tensorflow.contrib.learn.python.learn.utils import saved_model_export_utils\n",
    "from tensorflow.contrib.learn.python.learn import learn_runner\n",
    "\n",
    "PATTERN = \"00000-of-\"  # process only one of the shards, for testing purposes\n",
    "\n",
    "def train_and_evaluate(output_dir):\n",
    "    wide, deep = get_wide_deep()\n",
    "    estimator = tf.estimator.DNNLinearCombinedRegressor(\n",
    "                         model_dir=output_dir,\n",
    "                         linear_feature_columns=wide,\n",
    "                         dnn_feature_columns=deep,\n",
    "                         dnn_hidden_units=[64, 32])\n",
    "    train_spec=tf.estimator.TrainSpec(\n",
    "                         input_fn=read_dataset('train', PATTERN),\n",
    "                         max_steps=TRAIN_STEPS)\n",
    "    exporter = tf.estimator.FinalExporter('exporter',serving_input_fn)\n",
    "    eval_spec=tf.estimator.EvalSpec(\n",
    "                         input_fn=read_dataset('eval', PATTERN),\n",
    "                         steps=None,\n",
    "                         exporters=exporter)\n",
    "    tf.estimator.train_and_evaluate(estimator, train_spec, eval_spec)\n",
    "    \n",
    "shutil.rmtree('babyweight_trained', ignore_errors=True) # start fresh each time\n",
    "train_and_evaluate('babyweight_trained')"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Now that we have the TensorFlow code working on a subset of the data (in the code above, I was reading only the 00000-of-x file), we can package the TensorFlow code up as a Python module and train it on Cloud ML Engine.\n",
    "<p>\n",
    "<h2> Training on Cloud ML Engine </h2>\n",
    "<p>\n",
    "Training on Cloud ML Engine requires:\n",
    "<ol>\n",
    "<li> Making the code a Python package\n",
    "<li> Using gcloud to submit the training code to Cloud ML Engine\n",
    "</ol>\n",
    "<p>\n",
    "The code in model.py is the same as in the above cells. I just moved it to a file so that I could package it up as a module.\n",
    "(explore the <a href=\"babyweight/trainer\">directory structure</a>)."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "def read_dataset(prefix, pattern, batch_size=512):\n",
      "def get_wide_deep():\n",
      "def serving_input_fn():\n",
      "def experiment_fn(output_dir):\n",
      "def train_and_evaluate(output_dir):\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "grep \"^def\" babyweight/trainer/model.py"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "After moving the code to a package, make sure it works standalone. (Note the --pattern and --train_steps lines so that I am not trying to boil the ocean on my laptop). Even then, this takes about <b>a minute</b> in which you won't see any output ..."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "bucket=cloud-training-demos-ml\n"
     ]
    },
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "/usr/local/envs/py2env/lib/python2.7/site-packages/h5py/__init__.py:36: FutureWarning: Conversion of the second argument of issubdtype from `float` to `np.floating` is deprecated. In future, it will be treated as `np.float64 == np.dtype(float).type`.\n",
      "  from ._conv import register_converters as _register_converters\n",
      "INFO:tensorflow:Using default config.\n",
      "INFO:tensorflow:Using config: {'_save_checkpoints_secs': 600, '_session_config': None, '_keep_checkpoint_max': 5, '_task_type': 'worker', '_is_chief': True, '_cluster_spec': <tensorflow.python.training.server_lib.ClusterSpec object at 0x7f5cde543090>, '_save_checkpoints_steps': None, '_keep_checkpoint_every_n_hours': 10000, '_service': None, '_num_ps_replicas': 0, '_tf_random_seed': None, '_master': '', '_num_worker_replicas': 1, '_task_id': 0, '_log_step_count_steps': 100, '_model_dir': 'babyweight_trained/', '_save_summary_steps': 100}\n",
      "INFO:tensorflow:Running training and evaluation locally (non-distributed).\n",
      "INFO:tensorflow:Start train and evaluate loop. The evaluate will happen after 600 secs (eval_spec.throttle_secs) or training is finished.\n",
      "INFO:tensorflow:Create CheckpointSaverHook.\n",
      "2018-09-28 07:08:46.515993: I tensorflow/core/platform/cpu_feature_guard.cc:137] Your CPU supports instructions that this TensorFlow binary was not compiled to use: SSE4.1 SSE4.2 AVX AVX2 FMA\n",
      "INFO:tensorflow:Saving checkpoints for 1 into babyweight_trained/model.ckpt.\n",
      "INFO:tensorflow:loss = 75333.83, step = 1\n",
      "INFO:tensorflow:global_step/sec: 79.1769\n",
      "INFO:tensorflow:loss = 732.01196, step = 101 (1.263 sec)\n",
      "INFO:tensorflow:global_step/sec: 95.1179\n",
      "INFO:tensorflow:loss = 595.8302, step = 201 (1.051 sec)\n",
      "INFO:tensorflow:global_step/sec: 96.4323\n",
      "INFO:tensorflow:loss = 639.34, step = 301 (1.037 sec)\n",
      "INFO:tensorflow:global_step/sec: 97.082\n",
      "INFO:tensorflow:loss = 589.39966, step = 401 (1.030 sec)\n",
      "INFO:tensorflow:global_step/sec: 97.3062\n",
      "INFO:tensorflow:loss = 549.95276, step = 501 (1.028 sec)\n",
      "INFO:tensorflow:global_step/sec: 98.3283\n",
      "INFO:tensorflow:loss = 556.9101, step = 601 (1.017 sec)\n",
      "INFO:tensorflow:global_step/sec: 98.9581\n",
      "INFO:tensorflow:loss = 626.67505, step = 701 (1.011 sec)\n",
      "INFO:tensorflow:global_step/sec: 99.5258\n",
      "INFO:tensorflow:loss = 555.1832, step = 801 (1.005 sec)\n",
      "INFO:tensorflow:global_step/sec: 97.9521\n",
      "INFO:tensorflow:loss = 549.3536, step = 901 (1.021 sec)\n",
      "INFO:tensorflow:Saving checkpoints for 1000 into babyweight_trained/model.ckpt.\n",
      "INFO:tensorflow:Loss for final step: 605.63477.\n",
      "INFO:tensorflow:Starting evaluation at 2018-09-28-07:08:59\n",
      "INFO:tensorflow:Restoring parameters from babyweight_trained/model.ckpt-1000\n",
      "INFO:tensorflow:Finished evaluation at 2018-09-28-07:09:24\n",
      "INFO:tensorflow:Saving dict for global step 1000: average_loss = 1.1344848, global_step = 1000, loss = 580.8055\n",
      "INFO:tensorflow:Restoring parameters from babyweight_trained/model.ckpt-1000\n",
      "INFO:tensorflow:Assets added to graph.\n",
      "INFO:tensorflow:No assets to write.\n",
      "INFO:tensorflow:SavedModel written to: babyweight_trained/export/exporter/temp-1538118565/saved_model.pb\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "echo \"bucket=${BUCKET}\"\n",
    "rm -rf babyweight_trained\n",
    "export PYTHONPATH=${PYTHONPATH}:${PWD}/babyweight\n",
    "python -m trainer.task \\\n",
    "   --bucket=${BUCKET} \\\n",
    "   --output_dir=babyweight_trained \\\n",
    "   --job-dir=./tmp \\\n",
    "   --pattern=\"00000-of-\" --train_steps=1000"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Once the code works in standalone mode, you can run it on Cloud ML Engine.  Because this is on the entire dataset, it will take a while. The training run took about <b> 30 min </b> for me. You can monitor the job from the GCP console in the Cloud Machine Learning Engine section."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "gs://cloud-training-demos/babyweight/trained_model us-central1 babyweight_180928_070933\n",
      "jobId: babyweight_180928_070933\n",
      "state: QUEUED\n"
     ]
    },
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "Job [babyweight_180928_070933] submitted successfully.\n",
      "Your job is still active. You may view the status of your job with the command\n",
      "\n",
      "  $ gcloud ml-engine jobs describe babyweight_180928_070933\n",
      "\n",
      "or continue streaming the logs with the command\n",
      "\n",
      "  $ gcloud ml-engine jobs stream-logs babyweight_180928_070933\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "OUTDIR=gs://${BUCKET}/babyweight/trained_model\n",
    "JOBNAME=babyweight_$(date -u +%y%m%d_%H%M%S)\n",
    "echo $OUTDIR $REGION $JOBNAME\n",
    "#gcloud storage rm --recursive --continue-on-error $OUTDIR\n",    "gcloud ml-engine jobs submit training $JOBNAME \\\n",
    "   --region=$REGION \\\n",
    "   --module-name=trainer.task \\\n",
    "   --package-path=$(pwd)/babyweight/trainer \\\n",
    "   --job-dir=$OUTDIR \\\n",
    "   --staging-bucket=gs://$BUCKET \\\n",
    "   --scale-tier=STANDARD_1 \\\n",
    "   --runtime-version 1.4 \\\n",
    "   -- \\\n",
    "   --bucket=${BUCKET} \\\n",
    "   --output_dir=${OUTDIR} \\\n",
    "   --train_steps=100000"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Training finished with a RMSE of about 1 lb.  Obviously, this is our first model. We could probably add in some features and do some hyper-parameter tuning to get to a lower RMSE.  I'll leave that to you.  If you create a better model, I'd love to hear about it -- please do write a short blog post about what you did, and tweet it at me -- @lak_gcp."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "from google.datalab.ml import TensorBoard\n",
    "TensorBoard().start('gs://{}/babyweight/trained_model'.format(BUCKET))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "for pid in TensorBoard.list()['pid']:\n",
    "    TensorBoard().stop(pid)\n",
    "    print('Stopped TensorBoard with pid {}'.format(pid))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<table width=\"70%\">\n",
    "<tr><td><img src=\"weights.png\"/></td><td><img src=\"rmse.png\" /></tr>\n",
    "</table>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h2> Deploying the trained model </h2>\n",
    "<p>\n",
    "Deploying the trained model to act as a REST web service is a simple gcloud call."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "gs://cloud-training-demos-ml/babyweight/trained_model/export/exporter/\n",
      "gs://cloud-training-demos-ml/babyweight/trained_model/export/exporter/1538119053/\n",
      "gs://cloud-training-demos-ml/babyweight/trained_model/export/exporter/1538119270/\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "gcloud storage ls gs://${BUCKET}/babyweight/trained_model/export/exporter"   ]
  },
  {
   "cell_type": "code",
   "execution_count": 19,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Deleting and deploying babyweight soln from gs://cloud-training-demos-ml/babyweight/trained_model/export/exporter/1538119270/ ... this will take a few minutes\n"
     ]
    },
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "Created ml engine model [projects/cloud-training-demos/models/babyweight].\n",
      "Creating version (this might take a few minutes)......\n",
      "..........................................................................................done.\n"
     ]
    }
   ],
   "source": [
    "%bash\n",
    "MODEL_NAME=\"babyweight\"\n",
    "MODEL_VERSION=\"soln\"\n",
    "MODEL_LOCATION=$(gcloud storage ls gs://${BUCKET}/babyweight/trained_model/export/exporter/ | tail -1)\n",    "echo \"Deleting and deploying $MODEL_NAME $MODEL_VERSION from $MODEL_LOCATION ... this will take a few minutes\"\n",
    "#gcloud ml-engine versions delete ${MODEL_VERSION} --model ${MODEL_NAME}\n",
    "#gcloud ml-engine models delete ${MODEL_NAME}\n",
    "gcloud ml-engine models create ${MODEL_NAME} --regions $REGION\n",
    "gcloud ml-engine versions create ${MODEL_VERSION} --model ${MODEL_NAME} --origin ${MODEL_LOCATION} --runtime-version 1.4"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Once this has been created, it will display 'done'."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h2> Using the model to predict </h2>\n",
    "<p>\n",
    "Send a JSON request to the endpoint of the service to make it predict a baby's weight ... I am going to try out how well the model would have predicted the weights of our two kids and a couple of variations while we are at it ..."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 20,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "{\n",
      "    \"predictions\": [\n",
      "        {\n",
      "            \"predictions\": [\n",
      "                7.640133514404297\n",
      "            ]\n",
      "        }, \n",
      "        {\n",
      "            \"predictions\": [\n",
      "                7.189694499969482\n",
      "            ]\n",
      "        }, \n",
      "        {\n",
      "            \"predictions\": [\n",
      "                6.5124409675598145\n",
      "            ]\n",
      "        }, \n",
      "        {\n",
      "            \"predictions\": [\n",
      "                6.2403120040893555\n",
      "            ]\n",
      "        }\n",
      "    ]\n",
      "}\n"
     ]
    }
   ],
   "source": [
    "from googleapiclient import discovery\n",
    "from oauth2client.client import GoogleCredentials\n",
    "import json\n",
    "\n",
    "credentials = GoogleCredentials.get_application_default()\n",
    "api = discovery.build('ml', 'v1', credentials=credentials)\n",
    "\n",
    "request_data = {'instances':\n",
    "  [\n",
    "    {\n",
    "      'is_male': 'True',\n",
    "      'mother_age': 26.0,\n",
    "      'plurality': 'Single(1)',\n",
    "      'gestation_weeks': 39\n",
    "    },\n",
    "    {\n",
    "      'is_male': 'False',\n",
    "      'mother_age': 29.0,\n",
    "      'plurality': 'Single(1)',\n",
    "      'gestation_weeks': 38\n",
    "    },\n",
    "    {\n",
    "      'is_male': 'True',\n",
    "      'mother_age': 26.0,\n",
    "      'plurality': 'Triplets(3)',\n",
    "      'gestation_weeks': 39\n",
    "    },\n",
    "    {\n",
    "      'is_male': 'Unknown',\n",
    "      'mother_age': 29.0,\n",
    "      'plurality': 'Multiple(2+)',\n",
    "      'gestation_weeks': 38\n",
    "    },\n",
    "  ]\n",
    "}\n",
    "\n",
    "parent = 'projects/%s/models/%s/versions/%s' % (PROJECT, 'babyweight', 'soln')\n",
    "response = api.projects().predict(body=request_data, name=parent).execute()\n",
    "print(json.dumps(response, sort_keys = True, indent = 4))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "When I ran this, the four predictions for each of the requests in `request_data` above are 7.6, 7.2, 6.5, and 6.2 pounds. Yours may be different."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Copyright 2018 Google Inc. Licensed under the Apache License, Version 2.0 (the \"License\"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an \"AS IS\" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 2",
   "language": "python",
   "name": "python2"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 2
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython2",
   "version": "2.7.13"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}
